// @Title  请填写文件名称（需要改）
// @Description  请填写文件描述（需要改）
// @Author  请填写自己的真是姓名（需要改）  2021/4/28 14:32
// @Update  请填写自己的真是姓名（需要改）  2021/4/28 14:32
package ometa

import (
	"errors"
	"reflect"
	"strings"
	"taotaosql/pkg/utils"
)


// 获取表名称
func GetTableName(iface interface{}) string {
	/**
	实现了 func TableName() string 方法则调该方法获取表名，否则用结构体名称转表名
	*/
	tn, ok := iface.(TableName)
	if ok {
		return tn.TableName()
	}

	structVal := reflect.ValueOf(iface)
	structName := structVal.Type().Name()
	return utils.HumpStyle2Underline(structName)
}

/*
   获取某个struct的映射信息,提取struct的成员的标签中的column值
   @param structType 结构体的类型
   @param resultMapId resultMap的ID
   @return error 错误信息
*/
func GetResultMap(structType reflect.Type) (*ResultMapping, error) {
	if nil == structType {
		return nil, errors.New("structType is nil")
	}

	resultMapId := structType.Name() + "_resultMap"
	if structType.Kind() != reflect.Struct {
		return nil, errors.New("structType must be reflect.Struct")
	}

	numField := structType.NumField()
	columnPropMaps := make([]ColumnPropMapping, numField)
	resultMap := ResultMapping{
		Id:          resultMapId,
		StructType:  structType,
		ColPropMaps: columnPropMaps,
	}

	for i := 0; i < numField; i++ {
		columnPropMaps[i] = ColumnPropMapping{
			PropName: structType.Field(i).Name,
		}

		colName := structType.Field(i).Tag.Get("column")
		//有column标签则取标签，没有则属性名转字段名
		if "" == colName {
			columnPropMaps[i].ColName = utils.HumpStyle2Underline(structType.Field(i).Name)
		} else {
			columnPropMaps[i].ColName = colName
		}

		if "true" == structType.Field(i).Tag.Get("id") {
			columnPropMaps[i].IsId = true
		} else {
			columnPropMaps[i].IsId = false
		}

	}

	if 0 == len(columnPropMaps) {
		return nil, errors.New("no column tag value")
	}

	return &resultMap, nil

}

/*
   返回逗号分隔的列列表,例如：若别名为t,则返回 t.id,t.u,t.name

   @param *ResultMapping 映射信息
   @param tableAlia 表的别名
   @return string 列列表
   @return error 错误信息
*/
func GetColumnsSql(resultMap *ResultMapping, tableAlia string) (string, error) {
	if nil == resultMap {
		return "", errors.New("resultMap is nil")
	}

	colCount := len(resultMap.ColPropMaps)
	if 0 == colCount {
		return "", errors.New("no columns")
	}

	colNames := make([]string, colCount)
	for index, colPropMap := range resultMap.ColPropMaps {
		colNames[index] = colPropMap.ColName + " " + tableAlia
	}

	return strings.Join(colNames, ","), nil

}
